from django.shortcuts import render
from rest_framework.generics import GenericAPIView

from goods.models import SKU
from . import serializsers
from django_redis import get_redis_connection
from rest_framework.response import Response
import pickle
import base64
from rest_framework import status
class CartView(GenericAPIView):
    serializer_class = serializsers.CartSerializers

    #重写方法,让未登录用户也能访问该视图
    def perform_authentication(self, request):
        pass

    def post(self,request):
        #1,获取数据
        dict_data = request.data

        #2,获取序列化器
        serializer = self.get_serializer(data=dict_data)
        serializer.is_valid(raise_exception=True)

        #3,获取数据
        sku_id = serializer.data.get("sku_id")
        count = serializer.data.get("count")
        selected = serializer.data.get("selected",True)
        try:
            user = request.user
        except Exception as e:
            user = None

        #4,判断用户状态
        if user and request.user.is_authenticated:
            #4,1获取redis对象
            redis_conn = get_redis_connection("cart")

            #4,2增加购物车商品数量
            redis_conn.hincrby("cart_%s"%user.id,sku_id,count)

            #4,3判断是否选中
            if selected:
                redis_conn.sadd("cart_selected_%s"%user.id,sku_id)

            #4,4返回
            return Response(serializer.data)
        else:
            #5,1获取cookie购物车数据
            cookie_cart = request.COOKIES.get("cart")

            #5,2判断是否有购物车数据,转换字典格式
            cookie_dict = {}
            if cookie_cart:
                cookie_dict =pickle.loads(base64.b64decode(cookie_cart.encode()))

            #5,3累加
            if sku_id in cookie_dict:
                count += cookie_dict[sku_id].get("count",0)

            #5,4设置新的数据到字典
            cookie_dict[sku_id] = {
                "count":count,
                "selected":selected
            }

            #5,5将字典转换字符串,写入到cookie
            response = Response(status=200)
            cookie_cart = base64.b64encode(pickle.dumps(cookie_dict)).decode()
            response.set_cookie("cart",cookie_cart)

            #5,5返回响应
            return response

    def get(self,request):
        #1,获取用户数据
        try:
            user = request.user
        except Exception as e:
            user = None

        #2,判断用户登陆状态
        if user and request.user.is_authenticated:
            #1,获取redis中用户购物车数据
            redis_conn = get_redis_connection("cart")
            redis_cart_dict = redis_conn.hgetall("cart_%s"%user.id)
            redis_cart_selcted_list = redis_conn.smembers("cart_selected_%s"%user.id)

            #2,数据拼接
            sku_list = []
            for sku_id,count in redis_cart_dict.items():
                sku = SKU.objects.get(id=sku_id)
                sku_dict = {
                    "selected":sku_id in redis_cart_selcted_list,
                    "default_image_url":sku.default_image_url,
                    "name":sku.name,
                    "price":sku.price,
                    "count":int(count),
                    "id":sku.id
                }
                sku_list.append(sku_dict)

            #3,返回响应
            return Response(sku_list)
        else:
            #3,获取cookie中的数据
            cookie_cart = request.COOKIES.get("cart")

            #4,转换成字典
            cookie_dict = {}
            if cookie_cart:
                cookie_dict = pickle.loads(base64.b64decode(cookie_cart.encode()))

            #5,拼接数据
            sku_list = []
            for sku_id,count_selected  in cookie_dict.items():
                sku = SKU.objects.get(id=sku_id)
                sku_dict = {
                    "selected": count_selected["selected"],
                    "default_image_url": sku.default_image_url,
                    "name": sku.name,
                    "price": sku.price,
                    "count": int(count_selected["count"]),
                    "id":sku.id
                }
                sku_list.append(sku_dict)

            #6,返回响应
            return Response(sku_list)

    def put(self,request):
        #1,获取参数
        dict_data = request.data

        #2,获取序列化器,校验
        serializer = self.get_serializer(data=dict_data)
        serializer.is_valid(raise_exception=True)

        #3,获取数据
        sku_id = serializer.data.get("sku_id")
        count = serializer.data.get("count")
        selected = serializer.data.get("selected")
        try:
            user = request.user
        except Exception as e:
            user = None

        #4,判断用户登陆状态
        if user and request.user.is_authenticated:
            #4.1获取redis
            redis_conn = get_redis_connection("cart")

            #4.2修改
            redis_conn.hset("cart_%s"%user.id,sku_id,count)

            if selected:
                redis_conn.sadd("cart_selected_%s"%user.id,sku_id)
            else:
                redis_conn.srem("cart_selected_%s"%user.id,sku_id)

            #4.3返回
            return Response(serializer.data)
        else:
            #5.1获取cookie数据
            cookie_cart = request.COOKIES.get("cart")

            #5.2转换字典
            cookie_dict = {}
            if cookie_cart:
                cookie_dict = pickle.loads(base64.b64decode(cookie_cart.encode()))

            #5.3修改
            cookie_dict[sku_id] = {
                "count":count,
                "selected":selected
            }

            #5.4转换成字符串返回
            response = Response(serializer.data)
            cookie_cart = base64.b64encode(pickle.dumps(cookie_dict)).decode()
            response.set_cookie("cart",cookie_cart)
            return response

    def delete(self,request):
        #1,获取参数
        dict_data = request.data

        #2,创建序列化器,校验
        serializer = serializsers.CartDeleteSerializer(data=dict_data)
        serializer.is_valid(raise_exception=True)

        #3,获取数据
        sku_id = serializer.data.get("sku_id")

        try:
            user = request.user
        except Exception as e:
            user = None

        #4,判断用户状态
        if user and request.user.is_authenticated:
            #4.1删除redis中的数据
            redis_conn = get_redis_connection("cart")
            redis_conn.hdel("cart_%s"%user.id,sku_id)
            redis_conn.srem("cart_selected_%s"%user.id,sku_id)

            #4.2返回响应
            return Response(status=status.HTTP_204_NO_CONTENT)
        else:
            #5.1获取cookie中的数据
            cookie_cart = request.COOKIES.get("cart")

            #5.2转换字典
            cookie_dict = {}
            if cookie_cart:
                cookie_dict = pickle.loads(base64.b64decode(cookie_cart.encode()))

            #5.3删除
            if sku_id in cookie_dict:
                del cookie_dict[sku_id]

            #5.4返回响应
            response = Response(status=status.HTTP_204_NO_CONTENT)
            cookie_cart = base64.b64encode(pickle.dumps(cookie_dict)).decode()
            response.set_cookie("cart",cookie_cart)
            return response